上篇介紹了CSS Flex,這篇想來聊聊CSS grid到底是什麼東西
這裡想先給大家一個觀念:
Flex和grid它們並不是死對頭,它們是「好戰友」
它們的出現是相輔相成的,而不是為了互相取代對方
很多人會以為它們是死對頭,用了一個就不能用另一個
並不是喔!它們是可以一起使用的,全看當下需要什麼樣的排版形式
好,既然有了基本概念,那就來開始介紹grid吧!
Flex是一維的,排版方式是「由上到下」
而grid是二維的網格系統,可以「指定」內元件排版在網格內的「任何地方」
grid的常用語法可以分成以下兩種:
template (設定container內欲分配的網格空間)
grid-template-columns
/ grid-template-rows
/ grid-template
grid-template-area
column/row (設定內元件的位置)
grid-column-start
/ grid-column-end
/ grid-column
grid-row-start
/ grid-row-end
/ grid-row
grid-area
grid-column-gap
/ grid-row-gap
/ grid-gap
用講得太抽象了,我們來看範例吧!
這裡我有畫一張範例圖,上面有我們應該設定的值和線的名稱
那我們現在就把這張圖變成程式碼呈現出來吧!
首先,我們先看一下HTML和CSS的代碼
HTML:
<div class="grid_container">
<div class="box_red"></div>
<div class="box_green"></div>
<div class="box_yellow"></div>
<div class="box_blue"></div>
<div class="box_deepBlue"></div>
</div>
CSS:
.grid_container {
border:solid 7px darkgray;
width:330px;
height:420px;
display:grid;
}
.box_red {
background-color:red;
}
.box_green {
background-color:green;
}
.box_yellow {
background-color:yellow;
}
.box_blue {
background-color:blue;
}
.box_deepBlue {
background-color:deepskyblue;
}
template
現在我們要先把container的網格空間分配好,用的是grid-template-columns
和grid-template-rows
.grid_container {
grid-template-columns:[line_1] 30px [line2] 100px [column-3] 0.7fr [line4] 0.3fr [column-5];
grid-template-rows:[row-1] 100px [row-2] 150px [row-3] 0.2fr [row-4] 0.8fr [row-5];
}
這邊要和範例圖對照著看,[]內是線的名稱,而線與線之間是我們應分配的空間值fr
代表剩餘空間「欲分配的比例」,Ex:有一剩餘空間為100px,0.7fr
和0.3fr
代表將100px分成兩行,其行空間分別為70px
和30px
grid-template是grid-template-rows
和grid-template-columns
的縮寫
寫的順序為grid-template : grid-template-rows / grid-template-columns
所以你也可以寫成:
.grid_container {
grid-template:[row-1] 100px [row-2] 150px [row-3] 0.2fr [row-4] 0.8fr [row-5] / [line_1] 30px [line2] 100px [column-3] 0.7fr [line4] 0.3fr [column-5];
}
但我們非常不建議用grid-template縮寫,因為這樣可讀性會變很差
所以建議還是用grid-template-columns
和grid-template-rows
去分配空間
Grid-template-area會放在後面和grid-area一起介紹,請各位稍待片刻!
Column/row
既然我們已經把container的網格空間分配好,那就可以開始分配內元件的位置了!
用的是grid-column-start
和grid-column-end
,還有grid-row-start
和grid-row-end
首先,我們先看回範例圖,box_red的column是從column-3到column-5
,而row是從row-1到row-2
可寫成
.box_red {
grid-column-start:3;
grid-column-end:5;
grid-row-start:1;
grid-row-end:2;
}
box_green的column是從line_1到line4
,而row是從row-2到row-3
可寫成
.box_green {
grid-column-start:1;
grid-column-end:4;
grid-row-start:2;
grid-row-end:3;
}
依此類推,box_yellow、box_bule、box_deepBule可寫成
.box_yellow {
grid-column-start:2;
grid-column-end:4;
grid-row-start:3;
grid-row-end:4;
}
.box_blue {
grid-column-start:1;
grid-column-end:3;
grid-row-start:4;
grid-row-end:5;
}
.box_deepBlue {
grid-column-start:4;
grid-column-end:5;
grid-row-start:2;
grid-row-end:5;
}
結果如下圖所示:
grid-column是grid-column-start
和grid-column-end
的縮寫
而gird-row是gird-row-start
和grid-row-end
的縮寫
寫的順序為:grid-column:grid-column-start / grid-column-end
、grid-row:grid-row-start / grid-row-end
所以我們也可以將上述程式碼改寫成:
.box_red {
grid-column:3/5;
grid-row:1/2;
}
.box_green {
grid-column:1/4;
grid-row:2/3;
}
.box_yellow {
grid-column:2/4;
grid-row:3/4;
}
.box_blue {
grid-column:1/3;
grid-row:4/5;
}
.box_deepBlue {
grid-column:4/5;
grid-row:2/5;
}
也可以將線的數字改成「線的名字」,其得到的結果是一樣的
.box_red {
grid-column:column-3 / column-5;
grid-row:row-1 / row-2;
}
.box_green {
grid-column:line_1 / line4;
grid-row:row-2 / row-3;
}
.box_yellow {
grid-column:line2 / line4;
grid-row:row-3 / row-4;
}
.box_blue {
grid-column:line_1 / column-3;
grid-row:row-4 / row-5;
}
.box_deepBlue {
grid-column:line4 / column-5;
grid-row:row-2 / row-5;
}
那我們現在來講講grid-template-area
和grid-area
是什麼東西
我們現在container的網格佈局是4*4,所以總共被分成16格
我們可以用grid-template-area
去分別賜予它們名字,並且把內元件位置分配好
如果那格網格你想空著,可以用.
表示
.grid_container {
grid-template-areas:". . _red _red"
"_green _green _green _deepbule"
". _yellow _yellow _deepbule"
"_bule _bule . _deepbule";
}
再分別在box裡設置grid-area
.box_red {
grid-area:_red;
}
.box_green {
grid-area:_green;
}
.box_yellow {
grid-area:_yellow;
}
.box_blue {
grid-area:_bule;
}
.box_deepBlue {
grid-area:_deepbule;
}
得到結果會和剛剛一樣
而grid-area也可以是grid-row
和grid-column
的縮寫
寫的順序為grid-area:grid-row-start / grid-column-start / grid-row-end / grid-column-end
所以前面的box程式碼也可以寫成:
.box_red {
grid-area:1/3/2/5;
}
.box_green {
grid-area:2/1/3/4;
}
.box_yellow {
grid-area:3/2/4/4;
}
.box_blue {
grid-area:4/1/5/3;
}
.box_deepBlue {
grid-area:2/4/5/5;
}
如果想調整網格的間距,可用grid-column-gap
和grid-row-gap
增加線的寬度
.grid_container {
grid-column-gap:30px;
grid-row-gap:15px;
}
結果如下圖所示:
grid-gap是grid-row-gap
和grid-column-gap
的縮寫
寫的順序為grid-gap:grid-row-gap 「空格」 grid-column-gap
所以我們也可以將上述程式碼改寫成:
.grid_container {
grid-gap:15px 30px;
}
以上就是grid的常用語法介紹
有人會問,既然grid和Flex是相輔相成的,那能不能用和Flex相關的屬性去控制grid呢?
答案是可以的!但怕各位混淆,所以我決定放在下篇(Day 7)和大家介紹
這篇主要是希望大家能把grid的網格佈局搞清楚
先畫好網格、搞清楚如何控制內元件位置,才能開始進行排版R!
希望大家看完後能對grid更加了解
另外,這裡想和各位分享一個grid的小遊戲 (真的不是業配啦哈哈)
https://cssgridgarden.com/#zh-tw
是個種胡蘿蔔和清雜草的小遊戲,可以讓你快速理解grid的操作
想多了解grid的網格佈局的人可以去玩看看唷!
參考資料:
https://blog.techbridge.cc/2017/02/03/css-grid-intro/
我們非常建議最後上傳一次範例的程式碼,因為這樣可讀性會變很好。
使用grid-template-rows 和 grid-template-columns 設定網格空間 :
https://codepen.io/sxrtvbfb-the-bold/pen/JjqOmqj
使用 grid-template-area 設定網格空間 :
https://codepen.io/sxrtvbfb-the-bold/pen/wvbpKyx
需注意的是,使用不同方式設定容器,Grid排版結果會有差異。
原因是 grid-template-rows
和 grid-template-columns
可以設定
每條線與線間距 所以調整上更細緻一些。